package org.example.langchan4j.controller;

import dev.langchain4j.data.message.ImageContent;
import dev.langchain4j.data.message.TextContent;
import dev.langchain4j.data.message.UserMessage;
import dev.langchain4j.internal.Json;
import org.example.langchan4j.config.AiCodeHelper;
import org.example.langchan4j.config.AiCodeHelperService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.http.MediaType;
import org.springframework.http.ResponseEntity;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
import org.springframework.web.servlet.mvc.method.annotation.SseEmitter;
import org.springframework.web.servlet.mvc.method.annotation.StreamingResponseBody;

import java.io.IOException;
import java.io.OutputStreamWriter;
import java.nio.charset.StandardCharsets;
import java.util.List;
import java.util.Map;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;

@Controller
@RestController
@RequestMapping("/ai")
public class AiChatModel {
    @Autowired
    private AiCodeHelper aiCodeHelper;
    @Autowired
    private AiCodeHelperService aiCodeHelperService;

    private final ExecutorService executorService = Executors.newCachedThreadPool();

    @PostMapping("/chat")
    public String chat(@RequestBody Map<String, String> request) {
        String message = request.get("message");
        return aiCodeHelper.chat(message);
    }

    @PostMapping("/chatWithMessage")
    public String chatWithMessage(@RequestBody Map<String, String> request) {
        String url = request.get("url");
        UserMessage userMessage = UserMessage.from(
                TextContent.from("描述图片"),
                ImageContent.from(url)
        );
        String chatWithMessage = aiCodeHelper.chatWithMessage(userMessage);
        return chatWithMessage;
    }

    @PostMapping("/systemMessage")
    public String SystemMessage(@RequestBody Map<String, String> request) {
        String message = request.get("message");
        String systemMessage = aiCodeHelper.systemMessage(message);
        return systemMessage;
    }

    @PostMapping("/aiService")
    public String aiService(@RequestBody Map<String, String> request) {
        String message = request.get("message");
        String aiMessage = aiCodeHelperService.chat("defalut", message);
        return aiMessage;
    }

    @PostMapping("/chatMemory")
    public String chatMemory(@RequestBody Map<String, String> request) {
        String message = request.get("message");
        String aiMessage = aiCodeHelperService.chat("defalut", message);
        return aiMessage;
    }

    @PostMapping(value = "/chatForReport1", produces = MediaType.TEXT_PLAIN_VALUE)
    public StreamingResponseBody chatForReport1(@RequestBody Map<String, Object> request) {
        String content = (String) request.get("content");
        String language = (String) request.get("language");
        String model = (String) request.get("model");
        boolean stream = request.containsKey("stream") ? (boolean) request.get("stream") : true; // 默认启用流式

        return outputStream -> {
            try {
                AiCodeHelperService.PPTOutlineRequest pptRequest = new AiCodeHelperService.PPTOutlineRequest(
                        content, language, model, stream
                );

                AiCodeHelperService.Report report = aiCodeHelperService.chatForReport1(pptRequest);
                String reportContent = report.content();

                // 按行分割内容并逐行写入输出流
                String[] lines = reportContent.split("\n");
                for (String line : lines) {
                    outputStream.write((line + "\n").getBytes());
                    outputStream.flush();
                    Thread.sleep(50); // 控制输出速度
                }
            } catch (Exception e) {
                throw new RuntimeException(e);
            }
        };
    }

    @PostMapping(value = "/chatForReport2", produces = MediaType.APPLICATION_JSON_VALUE)
    public ResponseEntity<StreamingResponseBody> chatForReport2(@RequestBody Map<String, Object> request) {
        String content = (String) request.get("content");
        String language = request.containsKey("language") ? (String) request.get("language") : "中文";
        String model = request.containsKey("model") ? (String) request.get("model") : "default";
        boolean stream = request.containsKey("stream") ? (boolean) request.get("stream") : true;

        StreamingResponseBody responseBody = outputStream -> {
            try {
                AiCodeHelperService.Report1 report = aiCodeHelperService.chatForReport2(content);
                List<AiCodeHelperService.ReportSection> sections = report.sections();

                OutputStreamWriter writer = new OutputStreamWriter(outputStream, StandardCharsets.UTF_8);
                for (AiCodeHelperService.ReportSection section : sections) {
                    writer.write(Json.toJson(section) + "\n");
                    writer.flush();
                    Thread.sleep(100);
                }
            } catch (Exception e) {
                throw new RuntimeException("Streaming failed", e);
            }
        };

        return ResponseEntity.ok()
                .contentType(MediaType.APPLICATION_JSON)
                .body(responseBody);
    }
}
